﻿// 0822train01.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
//

#include <iostream>
#include <string>
#include <sstream>
#include <vector>
#include <queue>
#include <unordered_map>
#include <unordered_set>
#include <algorithm>
#include <limits>
#include <map>

using namespace std;

/*
 A、B 两个人玩一个数字比大小的游戏。
 在游戏开始前，两人各自拿到一个长度相同的数字序列，两个序列中的数字互不相同且随机排列。
 规则
1. 每一轮，A 和 B 各自从自己的序列中挑选一个数字进行比较：
   - 若 A 的数字大，A 得 1 分，B 扣 1 分；
   - 若 B 的数字大，B 得 1 分，A 扣 1 分；
   - 若相等，双方分数不变。
2. 用过的数字立即丢弃，不得再用。
3. 假设 A 事先知道 B 的整个序列，并且总是由 B 先选数字并明示给 A。
4. 目标：计算 A 可能获得的最大分数。

输入描述
第一行：一个整数 N，表示数字序列的长度。
第二行：N 个整数，A 的数字序列。
第三行：N 个整数，B 的数字序列。

输出描述
输出一个整数，表示 A 可能赢 B 的最大分数。

备注
采用贪心策略：能赢的一定要赢，不能赢的要尽量减少损失。

示例
输入
3
4 8 10
3 6 4

输出
3

说明
序列 A：4 8 10
序列 B：3 6 4
一种能达到最大分数 3 的对局顺序：
1) A 选 4，B 选 3 → A 得 1 分
2) A 选 8，B 选 6 → A 得 1 分
3) A 选 10，B 选 4 → A 得 1 分
最终 A 赢 3 分。
 */


void solve01(vector<int>&a_vec, vector<int>&b_vec)
{
    sort(a_vec.begin(), a_vec.end());
    sort(b_vec.begin(), b_vec.end());

    int left_a = 0, right_a = a_vec.size() - 1;
    int left_b = 0, right_b = b_vec.size() - 1;

    int result = 0;
    while (left_a <=right_a)
    {
        if (a_vec[right_a]>b_vec[right_b])
        {
            right_a--;
            right_b--;
            //战胜
            result += 1;
        }
        else if (a_vec[right_a]<b_vec[right_b])
        {
            //最弱a马出战，消耗b最强
            left_a++;
            right_b--;
            //战败
            result -= 1;
        }
        else
        {
            //最强马一致，最弱马互相消耗
            if (a_vec[left_a]>b_vec[left_b])
            {
                left_a++;
                left_b++;
                result += 1;
            }
            else
            {
                //最弱马战败
                //用a最弱换b最强
                if (b_vec[right_b] > a_vec[left_a])
                {
                    left_a++;
                    right_b--;
                    result += 1;
                }

            }

        }

    }

    cout << result;
}

/*
 单顺，又称顺子，最少5张牌，最多12张牌（3…A），不能有2，也不能有大小王，不计花色
 可用的牌：3 < 4 < 5 < 6 < 7 < 8 < 9 < 10 < J < Q < K < A < 2 < B(小王) < C(大王)，
 每种牌除大小王外有四种花色（共有13×4+2张牌）。

输入描述：  
第一行：当前手中的牌（用“-”连接）  
第二行：已经出过的牌（包括对手出的和自己出的牌，用“-”连接）

输出描述：  
最长的顺子（对手可能构成的最长的顺子，如果有相同长度的顺子，输出牌面最大的那一个）。  
如果无法构成顺子，则输出：NO-CHAIN

示例  
示例1  
输入  
3-3-3-4-4-5-5-6-7-8-9-10-J-Q-K-A-A-A-A  
4-5-6-7-8-8-8  
输出  
9-10-J-Q-K  

示例2  
输入  
3-3-3-3-8-8-8-8  
K-K-K-K  
输出  
NO-CHAIN  
 */

class Solution02
{
public:
    int card_vec_size = 15;
    vector<int>card_counts_vec;
    vector<vector<string>>total_vec;
    vector<string>track_vec;
    void generateCard()
    {
        vector<int>count_vec(card_vec_size, 0);
        for (int i=3; i<=14; i++)
        {
            count_vec[i] = 4;
        }
        card_counts_vec = count_vec;
    }
    string translateCard(string&card)
    {
        if (card == "J") return "11";
        if (card == "11") return "J";
        if (card == "Q") return "12";
        if (card == "12") return "Q";
        if (card == "K") return "13";
        if (card == "13") return "K";
        if (card == "A") return "14";
        if (card == "14") return "A";
        //不可组顺子 2BC
        if (card == "2") return "15";
        if (card == "B") return "16";
        if (card == "C") return "17";
        return card;
    }
    void sortResult()
    {
        sort(total_vec.begin(), total_vec.end(), [](vector<string>&a, vector<string>&b)
            {
            if (a.size()==b.size())
            {
                return a[0] > b[0];
            }
            return a.size() > b.size();
            });

    }
    void solve02(vector<string>&my_cards_vec, vector<string>&used_cards_vec)
    {
        generateCard();
        
        for (auto&card_str:my_cards_vec)
        {
            //去除自己手中的牌
            int num = stoi(translateCard(card_str));
            if (num< card_vec_size)
            {
                //防止越界
                card_counts_vec[num] -= 1;
            }
        }
        for (auto& card_str : used_cards_vec)
        {
            //去除已用过的牌
            int num = stoi(translateCard(card_str));
            if (num < card_vec_size)
            {
                //防止越界
                card_counts_vec[num] -= 1;
            }
        }
        //card_counts_vec剩下就是对手的牌
        for (int i=3; i< card_vec_size; i++)
        {
            int curr_count = card_counts_vec[i];
            string str_i = to_string(i);
            string curr_card = translateCard(str_i);
            if (curr_count>0)
            {
                track_vec.push_back(curr_card);
            }
            else
            {
                //中断了，清掉前面的
                track_vec.clear();
            }

            if (track_vec.size()>=5)
            {
                //保存顺子
                total_vec.push_back(track_vec);
            }

        }
        if (total_vec.empty())
        {
            cout << "NO-CHAIN";
            return;
        }

        //排序，长度相同输出牌面最大的
        sortResult();
        vector<string>result_vec = total_vec[0];
        string result = "";
        for (int i=0; i<result_vec.size();i++)
        {
            result += result_vec[i];
            if (i!=result_vec.size()-1)
            {
                result += "-";
            }
        }
        cout << result;
        //solve02
    }
};


/*
示例1

输入
5
10 5 0 1 3 2
30

输出
4
 */
void solve03(int level, vector<int>&count_vec, int target)
{
    map<int, int>level_map;

    for (int i=0;i<=level; i++)
    {
        int key = pow(2, i);
        if (i<count_vec.size())
        {
            level_map[key] = count_vec[i];
        }
    }
    int result = 0;
    int remainCount = 0;
    for (auto&map_item:level_map)
    {
        if (map_item.first>=target)
        {
            result += map_item.second;
        }
        else
        {
            remainCount += map_item.first * map_item.second;
        }
    }
    result += remainCount / target;
    cout << result;
    //solve03
}

int main()
{
	{
/*
输入
5
10 5 0 1 3 2
30
*/
        int level = 5, target = 30;
        vector<int>count_vec = { 10,5,0,1,3,2 };
        solve03(level, count_vec, target);

        return 0;
	}

	{
/*
输入  
3-3-3-4-4-5-5-6-7-8-9-10-J-Q-K-A-A-A-A  
4-5-6-7-8-8-8  
输出  
9-10-J-Q-K  
*/
        string my_cards_str, used_cards_str;
        getline(cin, my_cards_str);
        getline(cin, used_cards_str);
        vector<string>my_cards_vec;
        vector<string>used_cards_vec;
        //string my_cards_str = "3-3-3-4-4-5-5-6-7-8-9-10-J-Q-K-A-A-A-A";
        //string used_cards_str = "4-5-6-7-8-8-8 ";

        int pos = 0;
        stringstream oh_sstream(my_cards_str);
        string token;
        while (getline(oh_sstream,token,'-'))
        {
            my_cards_vec.push_back(token);
        }

        pos = 0;
        while (used_cards_str.find('-') != string::npos)
        {
            pos = used_cards_str.find('-');
            string curr_card = used_cards_str.substr(0, pos);
            used_cards_vec.push_back(curr_card);
            used_cards_str.erase(0, pos + 1);
        }
        used_cards_vec.push_back(used_cards_str);

        Solution02 solu;
        solu.solve02(my_cards_vec, used_cards_vec);

        return 0;
	}
/*
3
4 8 10
3 6 4
*/
    int vec_size;
    cin >> vec_size;
    vector<int>a_vec(vec_size);
    vector<int>b_vec(vec_size);
    for (int i=0; i<vec_size; i++)
    {
        cin >> a_vec[i];
    }
    for (int i = 0; i < vec_size; i++)
    {
        cin >> b_vec[i];
    }
    solve01(a_vec, b_vec);
    
}

// 运行程序: Ctrl + F5 或调试 >“开始执行(不调试)”菜单
// 调试程序: F5 或调试 >“开始调试”菜单

// 入门使用技巧: 
//   1. 使用解决方案资源管理器窗口添加/管理文件
//   2. 使用团队资源管理器窗口连接到源代码管理
//   3. 使用输出窗口查看生成输出和其他消息
//   4. 使用错误列表窗口查看错误
//   5. 转到“项目”>“添加新项”以创建新的代码文件，或转到“项目”>“添加现有项”以将现有代码文件添加到项目
//   6. 将来，若要再次打开此项目，请转到“文件”>“打开”>“项目”并选择 .sln 文件
